package com.fuego.creditsystemcommodity.service.impl;

import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.fuego.creditsystemcommodity.mapper.GoodOrderMapper;
import com.fuego.creditsystemcommodity.service.IGoodInfoService;
import com.fuego.creditsystemcommodity.service.IGoodOrderService;
import com.fuego.creditsystemcommodity.service.IGoodService;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.example.dto.Result;
import org.example.entity.GoodOrder;
import org.example.utils.RedisIdWorker;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.List;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author 虎哥
 * @since 2021-12-22
 */
@Slf4j
@Service
public class GoodOrderServiceImpl extends ServiceImpl<GoodOrderMapper, GoodOrder> implements IGoodOrderService {

    @Resource
    private IGoodInfoService goodInfoService;

    @Resource
    private IGoodService goodService;

    @Resource
    private StringRedisTemplate stringRedisTemplate;

    @Resource
    private RedisIdWorker redisIdWorker;

    @Override
    @Transactional
    public Result goodInfo(Long goodId, Long userId, Long amount) {
        // 验证参数
        if (goodId == null || userId == null || amount == null || amount <= 0) {
            return Result.fail("参数无效");
        }

        // 获取订单ID
        long orderId = redisIdWorker.nextId("goodorder");
        if (orderId == 0) {
            return Result.fail("生成订单ID失败");
        }

        // 检查库存
        String stockKey = "goodinfo:stock:" + goodId;
        String stockStr = stringRedisTemplate.opsForValue().get(stockKey);
        if (stockStr == null) {
            return Result.fail("库存信息不存在");
        }

        // 判断库存是否充足
        try {
            long stock = Long.parseLong(stockStr);
            if (stock < amount) {
                return Result.fail("库存不足，剩余: " + stock);
            }

            // 扣减Redis库存
            Long newStock = stringRedisTemplate.opsForValue().increment(stockKey, -amount);
            if (newStock == null || newStock < 0) {
                // 回滚Redis库存
                stringRedisTemplate.opsForValue().increment(stockKey, amount);
                return Result.fail("库存扣减失败");
            }

            // 创建订单对象
            GoodOrder goodOrder = new GoodOrder();
            int status = 1; // 已购买
            int payType = 1; // 默认支付类型
            goodOrder.setGoodId(goodId);
            goodOrder.setUserId(userId);
            goodOrder.setId(orderId);
            goodOrder.setStatus(status);
            goodOrder.setPayType(payType);
            goodOrder.setAmount(amount);
            goodOrder.setTotal(amount * goodService.getById(goodId).getCurrentPrice()/100 );
            goodOrder.setPurchaseTime(LocalDateTime.now());
            goodOrder.setCurrentPrice(goodService.getById(goodId).getCurrentPrice()/100);

            // 保存订单和更新数据库库存
            createGoodOrder(goodOrder);

            // 返回订单ID
            return Result.ok(orderId);
        } catch (NumberFormatException e) {
            log.error("库存解析失败，stockStr: {}", stockStr, e);
            return Result.fail("库存数据格式错误");
        } catch (Exception e) {
            log.error("订单创建失败，goodId: {}, userId: {}, amount: {}", goodId, userId, amount, e);
            // 回滚Redis库存
            stringRedisTemplate.opsForValue().increment(stockKey, amount);
            throw new RuntimeException("订单创建失败", e);
        }
    }

    @Transactional
    public void createGoodOrder(GoodOrder goodOrder) {
        // 扣减数据库库存
        boolean success = goodInfoService.update()
                .setSql("stock = stock - " + goodOrder.getAmount())
                .eq("good_id", goodOrder.getGoodId())
                .gt("stock", goodOrder.getAmount() - 1)
                .update();
        if (!success) {
            log.error("数据库库存扣减失败，goodId: {}, amount: {}", goodOrder.getGoodId(), goodOrder.getAmount());
            throw new RuntimeException("库存不足");
        }

        // 保存订单
        boolean saved = save(goodOrder);
        if (!saved) {
            log.error("订单保存失败，orderId: {}", goodOrder.getId());
            throw new RuntimeException("订单保存失败");
        }
    }

    @Override
    public Result queryAllOrders(Long userId) {
        if (userId == null) {
            return Result.fail("用户ID不能为空");
        }
        List<GoodOrder> goodOrders = getBaseMapper().queryAllOrders(userId);
        return Result.ok(goodOrders);
    }

    @Override
    @Transactional
    public Result refund(Long orderId) {
        if (orderId == null) {
            return Result.fail("订单ID不能为空");
        }
        GoodOrder order = this.query()
                .eq("id",orderId).list().get(0);

        if (order == null) {
            return Result.fail("订单不存在");
        }
        if (order.getStatus() == 2) {
            return Result.fail("订单已退款");
        }
        boolean success = this.update()
                .eq("id", orderId)
                .set("status", 2)
                .set("refund_time", LocalDateTime.now())
                .update();
        if (!success) {
            return Result.fail("退款失败");
        }
        // 恢复Redis库存
        String stockKey = "goodinfo:stock:" + order.getGoodId();
        stringRedisTemplate.opsForValue().increment(stockKey, order.getAmount());
        return Result.ok("退款成功，共计" + order.getAmount() + "件");
    }
}
